package org.jeecg.modules.demo.Kingdee.Job;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.kingdee.bos.webapi.sdk.K3CloudApi;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.jeecg.modules.demo.Kingdee.Receipt.entity.Receipt;
import org.jeecg.modules.demo.Kingdee.Receipt.service.IReceiptService;
import org.jeecg.modules.demo.Kingdee.util.AttachmentUploadUtil;
import org.quartz.Job;
import org.quartz.JobExecutionContext;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.io.File;
import java.util.List;

/**
 * 电子回单上传到金蝶系统的定时任务类
 * 功能：根据外部流水号将电子回单上传到金蝶系统中的对应应付单据
 * 
 * 工作流程：
 * 1. 查询所有未处理的回单记录(状态为空)
 * 2. 验证回单数据完整性(外部流水号、文件路径)
 * 3. 检查回单文件是否存在
 * 4. 根据外部流水号在金蝶系统中查找对应的应付单
 * 5. 将回单文件作为附件上传到查找到的应付单据中
 * 6. 更新回单处理状态
 */
@Slf4j
@Component
public class KDUploadReceiptJob implements Job {
    
    /**
     * 回单服务接口，用于查询和更新回单信息
     */
    @Autowired
    private IReceiptService receiptService;
    
    /**
     * 附件上传工具类，用于将文件上传到金蝶系统
     */
    @Autowired
    private AttachmentUploadUtil attachmentUploadUtil;

    /**
     * 定时任务执行方法
     * 
     * @param jobExecutionContext 定时任务执行上下文
     * @throws Exception 执行过程中可能抛出的异常
     */
    @SneakyThrows
    @Override
    public void execute(JobExecutionContext jobExecutionContext) {
        // 查询所有状态为空的回单记录（即未处理的回单）
        List<Receipt> receipts = receiptService.list(
            new com.baomidou.mybatisplus.core.conditions.query.QueryWrapper<Receipt>()
                .eq("status","未上传")
        );
        
        log.info("找到 {} 条状态为空的回单记录", receipts.size());
        
        // 遍历处理每一条回单记录
        for (Receipt receipt : receipts) {
            try {
                // 检查必要字段是否为空：外部请求流水号不能为空
                if (receipt.getExternalnum() == null || receipt.getExternalnum().isEmpty()) {
                    log.warn("回单ID {} 的外部请求流水号为空，跳过处理", receipt.getId());
                    continue;
                }
                
                // 检查必要字段是否为空：文件路径不能为空
                if (receipt.getPath() == null || receipt.getPath().isEmpty()) {
                    log.warn("回单ID {} 的文件路径为空，跳过处理", receipt.getId());
                    continue;
                }
                
                // 检查文件是否存在
                File file = new File(receipt.getPath());
                if (!file.exists()) {
                    log.warn("回单ID {} 的文件不存在: {}", receipt.getId(), receipt.getPath());
                    continue;
                }
                
                // 调用金蝶接口查询应付单中外部流水号(F_EXTERNALNUM)相匹配的数据
                //todo 此处的表单ID和字段Key需要根据实际情况进行修改
                String formId = "AP_Payable"; // 应付单表单ID
                String filterString = "F_ExternalNum = '" + receipt.getExternalnum() + "'";
                String queryJson = String.format(
                    "{\"FormId\":\"%s\",\"FieldKeys\":\"FID,FBillNo\",\"FilterString\":\"%s\"}",
                    formId, filterString
                );
                
                // 初始化K3CloudApi并执行查询
                K3CloudApi api = new K3CloudApi();
                String resultStr = api.billQuery(queryJson);
                
                // 解析查询结果
                List<JSONObject> resultList = JSONArray.parseArray(resultStr, JSONObject.class);
                
                // 如果未找到匹配的应付单，则记录警告日志并继续处理下一条
                if (resultList.isEmpty()) {
                    log.warn("未找到外部流水号 {} 对应的金蝶应付单", receipt.getExternalnum());
                    continue;
                }
                
                // 遍历查询结果，为每个匹配的应付单上传回单文件
                for (JSONObject item : resultList) {
                    String billId = item.getString("FID");    // 获取应付单主键ID
                    String billNo = item.getString("FBillNo"); // 获取应付单编号
                    
                    // 上传回单文件到金蝶单据
                    attachmentUploadUtil.uploadAttachment(
                        file.getName(),     // 文件名
                        formId,             // 表单ID
                        billNo,             // 单据编号
                        billId,             // 主键ID
                        file.toPath().toUri().toURL().openStream() // 文件输入流
                    );
                    
                    log.info("成功上传回单文件到金蝶单据: 单据ID={}, 单据编号={}, 文件名={}", 
                        billId, billNo, file.getName());
                }
                
                // 更新回单状态为"已上传"
                receipt.setStatus("已上传");
                receiptService.updateById(receipt);
                
                log.info("处理回单ID {}: 外部流水号={}, 文件路径={}", 
                    receipt.getId(), receipt.getExternalnum(), receipt.getPath());
                
            } catch (Exception e) {
                log.error("处理回单ID {} 时发生错误: ", receipt.getId(), e);
                // 更新状态为"处理失败"
                receipt.setStatus("处理失败");
                receiptService.updateById(receipt);
            }
        }
    }
}